import logging

from fastapi import FastAPI, Request
from fastapi.responses import StreamingResponse
import uuid, json
import app_loader
import threading
import asyncio

import m_p_config
import sender

from fastapi.middleware.cors import CORSMiddleware

app = FastAPI()


@app.post("/v1/chat/completions")
async def completions(request: Request):
    logging.info("接收到请求了")
    chat_id = f"chatcmpl-{str(uuid.uuid4())}"
    body = await request.json()  # 请求体
    proxy_model, app_config, user_prompt, stream = resolve_body(body)
    call_model, app_name, stream_mode, sys_prompt = resolve_sys_prompt(app_config)
    local_data = {
        'chat_id': chat_id,
        'proxy_model': proxy_model,
        'app_config': app_config,
        'stream_mode': stream_mode,
        'user_prompt': user_prompt,
        'call_model': call_model,
        'app_name': app_name,
        'sys_prompt': sys_prompt,
        'stream': stream
    }
    current_app = app_loader.get_app(app_name)
    msgs_list = current_app.get_msgs_list(local_data)   # 这是一个可以包含多个消息的[]

    async def do_call_model(use_model, ms_list, stream:bool, current_app,res_model):
        for ms in ms_list:
            before, completion, after = sender.send(model_name=use_model,is_stream=stream,ms= ms)
            if before is not None and before != '':
                yield before
                await asyncio.sleep(0.001)
            sse_res = current_app.resolve_completion(completion,chat_id,False,res_model)
            yield sse_res
            await asyncio.sleep(0.001)
            if after is not None and after != '':
                yield after
                await asyncio.sleep(0.001)
        sse_end = current_app.create_end_sse_response(chat_id=chat_id, is_stream=stream, model=res_model)
        if sse_end is not None and sse_end != '':
            yield sse_end
            await asyncio.sleep(0.001)

    response = StreamingResponse(do_call_model(call_model, msgs_list, stream=stream, current_app=current_app, res_model=proxy_model), media_type="text/event-stream")
    return response



def resolve_sys_prompt(system_prompt):
    return system_prompt['call_model'],  system_prompt['app'], system_prompt['stream_mode'], system_prompt['sys_prompt']


def resolve_body(body):  # 解析body
    messages = body['messages']
    proxy_model = body['model']  # 代理的model的名称
    stream = body['stream']
    app_config, user_prompt = '', ''
    for message in messages:
        if message['role'] == 'system':
            content = str(message['content'])
            app_config = json.loads(content)  # 系统提示词
        if message['role'] == 'user':
            user_prompt = str(message['content'])  # 用户输入

    return proxy_model, app_config, user_prompt, stream



# 注意：下面的代码应该在 if __name__ == "__main__": 块中
if __name__ == "__main__":
    import uvicorn
    # 添加跨域中间件
    app.add_middleware(
        CORSMiddleware,
        allow_origins=["*"],  # 允许所有来源的请求
        allow_credentials=True,
        allow_methods=["*"],  # 允许所有 HTTP 方法
        allow_headers=["*"],  # 允许所有请求头
    )

    uvicorn.run(app, host="0.0.0.0", port=m_p_config.getConfig()["server"]['port'])